Semantik Web • Hafta 02
XML & XML Schema
Yapılandırılmış veri gösterimi, XSD ile doğrulama ve alerji verisinin XML modeli
Lisansüstü Semantik Web Dersi • CMPE 583
Hafta 02 • Kazanımlar
Bu hafta sonunda
- Well-formed ve valid XML ayrımını uygulamalı olarak yapabileceksiniz.
- Alerji verisini element/attribute kararlarını gerekçelendirerek XML'de modelleyebileceksiniz.
- XSD ile veri tipi, facet, cardinality ve anahtar kısıtları yazabileceksiniz.
- Java ile bir XML belgesini şemaya karşı doğrulayabileceksiniz.
- XML'in ağaç modelinin RDF'in graf modeline neden yetmediğini açıklayabileceksiniz.
Geçen haftadan hatırlatma
- Belge Web'i sunumu, Veri Web'i anlamı kodlar.
- Yığın: IRI → XML → RDF → RDFS → OWL → kural/sorgu.
- Projede risk zinciri: Person → Product → FoodAdditives → Allergy.
- Bu hafta yığının ikinci basamağındayız: sözdizimi ve doğrulama.
Bu haftanın çıktısı
products.xml
persons.xml
allergy.xsd
Validate.java
01
Ödev 1'in Çözümü
Ortam kurulumu, ontoloji envanteri ve kavram ayrımı.
Çözüm 1.1 — Ortamın doğrulanması
$ java -version
openjdk version "1.8.0_392"
$ mvn -v
Apache Maven 3.9.6
Protégé 5.6.4
Tabs: Entities · Individuals
SWRLTab · OntoGraf
| Kontrol | Beklenen kanıt |
| Protégé açılıyor | Başlık çubuğunda sürüm |
| SWRLTab görünür | Sekme ekran görüntüsü |
| OWL dosyası açılıyor | Sınıf ağacı doldu |
| JDK / Maven | Sürüm çıktısı |
SWRLTab görünmüyorsa: File → Check for plugins → SWRLTab ve SWRLAPI eklentileri kurulup Protégé yeniden başlatılır.
Çözüm 1.2 — ALLERGY_FIXED.owl envanteri
| Varlık türü | Sayı | Örnekler |
| Sınıf | 6 | Person, Product, FoodAdditives, Allergy, Adult, PersonAtRisk |
| Nesne özelliği | 9 | Contain, Triggers, hasAllergy, ChooseProduct, Effected_Allergen + 4 alt özellik |
| Veri özelliği | 6 | hasName, hasAge, hasWeight, hasHeight, hasBMI, hasProductName |
| Birey | 17 | 4 kişi, 4 ürün, 5 katkı, 4 alerji |
| SWRL kuralı | 7 | S1 … S7 |
| Ayrıklık aksiyomu | 1 | AllDisjointClasses (4 üst sınıf) |
Adult ve PersonAtRisk sınıflarının bildirilmiş üyesi yoktur; üyelik kurallardan gelir.
Çözüm 1.3 — Sınıf mı, birey mi?
| Terim | Doğru modelleme | Gerekçe |
| Katkı maddesi | Sınıf (FoodAdditives) | Bir tür, üyeleri var |
| Nisin | Birey | Tek, belirli bir madde |
| Laktoz alerjisi | Birey (Lactose) | Alerji sınıfının belirli bir üyesi |
| Ürün | Sınıf | Barkodlu bireyleri kapsar |
| Eti Chocolate | Birey + hasProductName | Barkod kimliktir, ad veridir |
| Riskli kişi | Sınıf, kuralla doldurulur | Üyelik hesaplanır, bildirilmez |
Çözüm 1.4 — EAN_00005'in modellenmesi
EAN_00005 a Product ;
Contain Whey_Protein , Wheat_Starch ;
hasProductName "Protein Biscuit" .
Whey_Protein a FoodAdditives ;
Triggers Lactose .
Wheat_Starch a FoodAdditives ;
Triggers Gluten .
TC_004 (Egg, Gluten alerjisi) bu ürünü seçerse:
S6 → Effected_Allergen(TC_004, Wheat_Starch)
S7 → PersonAtRisk(TC_004)
Whey_Protein tetiklemez: TC_004'ün laktoz alerjisi yoktur — kural gövdesindeki hasAllergy(?p, ?al) bağlanmaz.
02
XML Temelleri
Ağaç modeli, well-formed kuralları, namespace.
XML nedir?
- Veriyi etiketlerle işaretleyen, uygulamadan bağımsız bir metin biçimi.
- Sabit bir etiket kümesi yoktur; etiketleri alan uzmanı tanımlar.
- Yapıyı taşır, anlamı taşımaz — anlam şemada ve uygulamada kalır.
<?xml version="1.0" encoding="UTF-8"?>
<product ean="EAN_00004">
<name>Eti Chocolate</name>
<additives>
<additive>Nisin</additive>
</additives>
</product>
Well-formed olmanın koşulları
- Tek bir kök element olmalı.
- Her açılan etiket kapanmalı.
- İç içe geçmeler doğru sırada olmalı.
- Etiket adları büyük/küçük harfe duyarlıdır.
- Attribute değerleri tırnak içinde olmalı.
<!-- HATALI -->
<product ean=EAN_00004> ← tırnak yok
<Name>Eti</name> ← harf uyumsuz
<additives><additive>Nisin
</additives></additive> ← sıra bozuk
</product>
Well-formed olmayan bir belgeyi hiçbir ayrıştırıcı okumaz — doğrulamadan önceki asgari koşuldur.
Bir XML belgesinin parçaları
<?xml version="1.0" encoding="UTF-8"?> ← prolog
<!-- Alerji projesi ürün kataloğu --> ← yorum
<products count="4"> ← kök element + attribute
<product ean="EAN_00003"> ← alt element
<name>Dardanel Ton</name> ← metin (PCDATA)
<additive ref="Casein"/> ← boş element
</product>
</products>
Belge bir ağaçtır: her düğümün tek ebeveyni vardır. Bu kısıt, Hafta 03'te RDF'e geçme nedenimiz olacak.
Element mi, attribute mü?
Attribute ağırlıklı
<person tc="TC_001" name="Ayse"
age="38" weight="67.5"
height="1.68"/>
Kısa; ama tekrarlanamaz ve yapı eklenemez.
Element ağırlıklı
<person tc="TC_001">
<name>Ayse</name>
<age>38</age>
<allergy ref="Lactose"/>
<allergy ref="Fish"/>
</person>
Çoklu değer ve genişleme mümkün.
Kural: kimlik ve meta bilgi attribute, alan verisi element. Bir kişinin birden çok alerjisi olabildiği için alerji element olmalıdır.
Namespace: aynı ad, farklı anlam
<cat:products
xmlns:cat="http://EMU/catalog#"
xmlns:med="http://EMU/medical#">
<cat:product ean="EAN_00003">
<cat:name>Dardanel Ton</cat:name>
<med:risk level="high"/>
</cat:product>
</cat:products>
- xmlns:önek="IRI" bildirimi ile ad çakışması çözülür.
- Anlamı belirleyen önek değil, IRI'dir.
- Öneksiz bildirim (xmlns=) varsayılan namespace'i belirler.
- Projedeki OWL dosyası da aynı mekanizmayı kullanır: rdf:, owl:, swrl:.
Projenin XML başlığı
<rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:xsd="http://www.w3.org/2001/XMLSchema#"
xmlns:rdfs="http://www.w3.org/2000/01/rdf-schema#"
xmlns:owl="http://www.w3.org/2002/07/owl#"
xml:base="http://EMU/AllergyOntology"
xmlns="http://EMU/AllergyOntology#"
xmlns:swrl="http://www.w3.org/2003/11/swrl#">
| Önek | Rolü |
| rdf, rdfs | Graf ve sözlük sözdizimi |
| owl | Ontoloji yapıları |
| xsd | Veri tipleri (int, double, string) |
| swrl | Kural aksiyomları |
| (varsayılan) | Projenin kendi terimleri: Person, Nisin … |
Özel karakterler ve CDATA
| Karakter | Entity |
| < | < |
| > | > |
| & | & |
| " | " |
| ' | ' |
<ingredients>
Süt & kakao içerir
</ingredients>
<label><![CDATA[
E322 (soya lesitini) < 0.5%
]]></label>
Gıda etiketlerinde yüzde ve "&" sık geçer; ayrıştırma hatalarının en yaygın kaynağı budur.
Kodlama: Türkçe karakter tuzakları
<?xml version="1.0" encoding="UTF-8"?>
<product ean="EAN_00006">
<name>Ülker Çikolatalı Gofret</name>
<note>Süt içerir · %30 kakao</note>
</product>
<!-- ISO-8859-9 olarak kaydedilirse: -->
<!-- Ülker Çikolatalı -->
| Tuzak | Sonuç |
| Bildirim UTF-8, dosya ANSI | Ayrıştırma hatası |
| BOM'lu UTF-8 | "Content is not allowed in prolog" |
| ı / İ dönüşümü | Java'da Locale.ROOT kullanın |
| IRI'de Türkçe harf | Yerel adları ASCII tutun |
Projede kural: etiket metni Türkçe olabilir, IRI yerel adı daima ASCII (Soy_Lecitin, etiket ise "Soya lesitini").
Belgenin ağaç modeli
products
├── product @ean=EAN_00003
│ ├── name "Dardanel Ton"
│ ├── additive @ref=Casein
│ └── additive @ref=Sodium_Ascorbite
└── product @ean=EAN_00004
├── name "Eti Chocolate"
├── additive @ref=Nisin
└── additive @ref=Soy_Lecitin
Katkı maddesinin hangi alerjiyi tetiklediği bu ağaçta yoktur; başka bir belgeye ref ile işaret ediyoruz — bağı uygulama kurar.
Örnek: products.xml
<?xml version="1.0" encoding="UTF-8"?>
<products xmlns="http://EMU/allergy/catalog"
count="4">
<product ean="EAN_00001">
<name>ETI Cracker</name>
<additive ref="Alginic_Acid"/>
</product>
<product ean="EAN_00002">
<name>Ulker Damak</name>
<additive ref="Phospore"/>
<additive ref="Soy_Lecitin"/>
</product>
<product ean="EAN_00003">
<name>Dardanel Ton</name>
<additive ref="Casein"/>
<additive ref="Sodium_Ascorbite"/>
</product>
<product ean="EAN_00004">
<name>Eti Chocolate</name>
<additive ref="Ascorbic_Acid"/>
<additive ref="Nisin"/>
<additive ref="Soy_Lecitin"/>
</product>
</products>
Katkılar ref ile ayrı belgeye işaret eder; ürün ile alerji arasında doğrudan bağ yoktur.
Örnek: additives.xml
<additives xmlns="http://EMU/allergy/catalog">
<additive id="Nisin" code="E234">
<label>Nisin</label>
<triggers allergy="Lactose"/>
</additive>
<additive id="Casein" code="E290">
<label>Casein</label>
<triggers allergy="Lactose"/>
</additive>
<additive id="Soy_Lecitin" code="E322">
<label>Soy Lecithin</label>
<triggers allergy="Egg"/>
</additive>
<additive id="Ascorbic_Acid" code="E300">
<label>Ascorbic Acid</label>
</additive>
</additives>
Ascorbic_Acid için triggers yoktur — bu, ontolojideki durumun aynısıdır.
XML'de bu "eksiklik" sadece bir boşluktur. OWL'da ise açık dünya gereği "bilinmiyor" anlamına gelir — aynı veri, iki farklı yorum.
Örnek: persons.xml
<persons xmlns="http://EMU/allergy/profile">
<person tc="TC_001">
<name>Ayse</name>
<age>38</age>
<weight unit="kg">67.5</weight>
<height unit="m">1.68</height>
<allergy ref="Lactose"/>
<choice ean="EAN_00004"/>
</person>
<person tc="TC_003">
<name>MEHMET</name>
<age>35</age>
<weight unit="kg">93.0</weight>
<height unit="m">1.87</height>
<allergy ref="Fish"/>
<allergy ref="Lactose"/>
<choice ean="EAN_00003"/>
</person>
</persons>
BMI burada yok: hesaplanan değerler kaynak veride tutulmaz — Hafta 07'de S4 kuralı üretecek.
03
Doğrulama: DTD ve XML Schema
Veri tipleri, kısıtlar, anahtarlar ve hata mesajlarını okumak.
Well-formed ile valid arasındaki fark
| Boyut | Well-formed | Valid |
| Neyi denetler | Sözdizimi | Şemaya uygunluk |
| Referans | XML 1.0 kuralları | DTD / XSD belgesi |
| "age=abc" | Geçerli | Hata: int beklenir |
| Bilinmeyen element | Geçerli | Hata |
| Zorunlu alan eksik | Geçerli | Hata |
Projede etiket verisi dış kaynaktan geldiği için doğrulama zorunludur: ontolojiye kirli veri girmesi, yanlış risk çıkarımı üretir.
DTD ile doğrulama ve sınırları
<!ELEMENT products (product+)>
<!ELEMENT product (name, additive*)>
<!ATTLIST product ean ID #REQUIRED>
<!ELEMENT name (#PCDATA)>
<!ELEMENT additive EMPTY>
<!ATTLIST additive ref IDREF #REQUIRED>
- Veri tipi yok: age "abc" olabilir.
- Namespace desteği yok.
- Sayı aralığı, desen, ondalık kısıt yazılamaz.
- Kendisi XML değildir; araçla işlenmesi zor.
Bu nedenle projede XSD kullanacağız; DTD'yi yalnızca eski belgeleri okumak için biliyoruz.
XML Schema belgesinin iskeleti
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns="http://EMU/allergy/catalog"
targetNamespace="http://EMU/allergy/catalog"
elementFormDefault="qualified">
<xs:element name="products" type="ProductsType"/>
<!-- tip tanımları burada -->
</xs:schema>
targetNamespace, şemanın hangi namespace'i tanımladığını söyler; belge de aynı namespace'i kullanmalıdır.
Yerleşik veri tipleri
| XSD tipi | Örnek değer | Projedeki alan |
| xs:string | "Eti Chocolate" | hasName, hasProductName |
| xs:int | 38 | hasAge |
| xs:double | 67.5 | hasWeight, hasHeight, hasBMI |
| xs:boolean | true | etiket doğrulandı mı |
| xs:date | 2026-09-08 | son tüketim tarihi |
| xs:ID / xs:IDREF | EAN_00004 | barkod ve referans |
Aynı tip adları OWL tarafında da geçer: rdfs:range = &xsd;double. XSD tipleri iki dünyanın ortak sözlüğüdür.
Kendi tipinizi tanımlayın: facet'ler
<xs:simpleType name="AgeType">
<xs:restriction base="xs:int">
<xs:minInclusive value="0"/>
<xs:maxInclusive value="120"/>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="WeightType">
<xs:restriction base="xs:double">
<xs:minExclusive value="0"/>
<xs:maxInclusive value="400"/>
</xs:restriction>
</xs:simpleType>
| Facet | İşi |
| minInclusive | Alt sınır (dahil) |
| maxExclusive | Üst sınır (hariç) |
| length | Uzunluk |
| pattern | Düzenli ifade |
| enumeration | İzinli değer kümesi |
| fractionDigits | Ondalık basamak |
Enumeration: alerji tipleri
<xs:simpleType name="AllergyType">
<xs:restriction base="xs:string">
<xs:enumeration value="Lactose"/>
<xs:enumeration value="Gluten"/>
<xs:enumeration value="Egg"/>
<xs:enumeration value="Fish"/>
</xs:restriction>
</xs:simpleType>
XSD burada kapalı dünya kurar: listede olmayan değer hatadır.
OWL karşılığı owl:oneOf ile yazılabilir; ancak projede alerjileri birey olarak tuttuk, çünkü yeni alerji türü eklemek şema değişikliği gerektirmemeli.
Pattern: barkod ve kimlik biçimi
<xs:simpleType name="EanType">
<xs:restriction base="xs:string">
<xs:pattern value="EAN_[0-9]{5}"/>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="TcType">
<xs:restriction base="xs:string">
<xs:pattern value="TC_[0-9]{3}"/>
</xs:restriction>
</xs:simpleType>
| Değer | EanType sonucu |
| EAN_00004 | Geçerli |
| EAN_4 | Hata — beş hane gerekli |
| ean_00004 | Hata — büyük harf gerekli |
Complex type: ürün
<xs:complexType name="ProductType">
<xs:sequence>
<xs:element name="name" type="xs:string"/>
<xs:element name="additive" type="AdditiveRefType"
minOccurs="0" maxOccurs="unbounded"/>
</xs:sequence>
<xs:attribute name="ean" type="EanType" use="required"/>
</xs:complexType>
<xs:complexType name="AdditiveRefType">
<xs:attribute name="ref" type="xs:string" use="required"/>
</xs:complexType>
minOccurs="0": katkısı bildirilmemiş ürün de geçerlidir — veri eksikliği şemayı kırmaz.
sequence, choice, all
| Yapı | Anlamı | Alerji örneği |
| sequence | Belirtilen sırada hepsi | name sonra additive listesi |
| choice | Yalnızca biri | ya ean ya internalCode ile kimlik |
| all | Hepsi, sıra serbest | weight, height, age |
| group | Yeniden kullanılabilir küme | ölçüm bloğu |
<xs:choice>
<xs:element name="ean" type="EanType"/>
<xs:element name="internalCode" type="xs:string"/>
</xs:choice>
Sayı kısıtları
| Bildirim | Anlamı |
| minOccurs="1" | Zorunlu (varsayılan) |
| minOccurs="0" | İsteğe bağlı |
| maxOccurs="unbounded" | Sınırsız tekrar |
| use="required" | Zorunlu attribute |
OWL karşılığı
Product ⊑ ≥1 Contain.FoodAdditives
XSD kısıtı veriyi reddeder; OWL kısıtı çıkarım üretir. Aynı cümle, iki farklı davranış — Hafta 05'te ayrıntılı.
key ve keyref: referans bütünlüğü
<xs:element name="catalog" type="CatalogType">
<xs:key name="additiveKey">
<xs:selector xpath="additives/additive"/>
<xs:field xpath="@id"/>
</xs:key>
<xs:keyref name="additiveRef" refer="additiveKey">
<xs:selector xpath="products/product/additive"/>
<xs:field xpath="@ref"/>
</xs:keyref>
</xs:element>
Böylece <additive ref="Nisiin"/> gibi bir yazım hatası doğrulamada yakalanır — ontolojiye yanlış birey girmesi engellenir.
Tam şema: allergy.xsd
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://EMU/allergy/catalog"
xmlns="http://EMU/allergy/catalog"
elementFormDefault="qualified">
<xs:element name="products">
<xs:complexType>
<xs:sequence>
<xs:element name="product" type="ProductType"
maxOccurs="unbounded"/>
</xs:sequence>
<xs:attribute name="count" type="xs:int"/>
</xs:complexType>
</xs:element>
<xs:complexType name="ProductType">
<xs:sequence>
<xs:element name="name" type="xs:string"/>
<xs:element name="additive"
type="AdditiveRefType" minOccurs="0"
maxOccurs="unbounded"/>
</xs:sequence>
<xs:attribute name="ean" type="EanType"
use="required"/>
</xs:complexType>
<xs:simpleType name="EanType">
<xs:restriction base="xs:string">
<xs:pattern value="EAN_[0-9]{5}"/>
</xs:restriction>
</xs:simpleType>
</xs:schema>
Doğrulama hatalarını okumak
<product ean="EAN_4">
cvc-pattern-valid: 'EAN_4' is not facet-valid with respect to pattern 'EAN_[0-9]{5}'
<age>abc</age>
cvc-datatype-valid.1.2.1: 'abc' is not a valid value for 'int'
<product> <!-- ean yok -->
cvc-complex-type.4: Attribute 'ean' must appear on element 'product'
Mesajın başındaki cvc-* kodu hangi kuralın ihlal edildiğini söyler; hata ayıklamanın en hızlı yolu bu koddur.
Java ile doğrulama: Validate.java
import javax.xml.XMLConstants;
import javax.xml.validation.*;
import org.xml.sax.SAXException;
import java.io.File;
public class Validate {
public static void main(String[] a) throws Exception {
SchemaFactory sf = SchemaFactory.newInstance(
XMLConstants.W3C_XML_SCHEMA_NS_URI);
Schema schema = sf.newSchema(new File("allergy.xsd"));
Validator v = schema.newValidator();
try {
v.validate(new javax.xml.transform.stream.StreamSource(
new File("products.xml")));
System.out.println("products.xml GECERLI");
} catch (SAXException e) {
System.out.println("HATA: " + e.getMessage());
}
}
}
Ayrıştırıcı seçimi: DOM, SAX, StAX
| Model | Yaklaşım | Bellek | Alerji projesinde |
| DOM | Belgeyi ağaç olarak yükler | Yüksek | Küçük katalog, XPath ile gezinme |
| SAX | Olay tabanlı, tek geçiş | Çok düşük | Binlerce ürünlü market dökümü |
| StAX | Çekmeli (pull) akış | Düşük | Kısmi okuma, erken durma |
| JAXB | Nesneye eşleme | Orta | Product/Person sınıflarına bağlama |
Kural: veri belleğe sığıyorsa ve rastgele erişim gerekiyorsa DOM; akış hâlinde büyük veri geliyorsa SAX ya da StAX.
Java + DOM: katalogu okumak
DocumentBuilderFactory f =
DocumentBuilderFactory.newInstance();
f.setNamespaceAware(true);
Document doc = f.newDocumentBuilder()
.parse(new File("products.xml"));
NodeList ps = doc.getElementsByTagNameNS(
"http://EMU/allergy/catalog", "product");
for (int i = 0; i < ps.getLength(); i++) {
Element p = (Element) ps.item(i);
String ean = p.getAttribute("ean");
NodeList as = p.getElementsByTagNameNS("*","additive");
for (int j = 0; j < as.getLength(); j++)
System.out.println(ean + " Contain " +
((Element) as.item(j)).getAttribute("ref"));
}
EAN_00001 Contain Alginic_Acid
EAN_00002 Contain Phospore
EAN_00002 Contain Soy_Lecitin
EAN_00003 Contain Casein
EAN_00003 Contain Sodium_Ascorbite
EAN_00004 Contain Ascorbic_Acid
EAN_00004 Contain Nisin
EAN_00004 Contain Soy_Lecitin
Bu çıktı doğrudan üçlü biçimindedir — Hafta 08'de aynı satırlar OWL API ile aksiyoma dönüşecek.
Java + SAX: akış hâlinde okumak
SAXParserFactory.newInstance().newSAXParser().parse(
new File("market_dump.xml"),
new DefaultHandler() {
String ean;
public void startElement(String u, String l, String q, Attributes at) {
if ("product".equals(l)) ean = at.getValue("ean");
if ("additive".equals(l)) risk(ean, at.getValue("ref"));
}
});
// risk(): katki Lactose tetikliyorsa uyari listesine ekle
SAX belgeyi bellekte tutmaz: 500 MB'lık bir market dökümü sabit bellekle taranabilir; karşılığında geri dönüp gezinemezsiniz.
XPath ile veri seçmek
| XPath | Sonuç |
| /products/product/@ean | Tüm barkodlar |
| //product[additive/@ref='Nisin']/name | Nisin içeren ürün adları |
| count(//product[@ean='EAN_00004']/additive) | 3 |
| //person[age>=18]/name | Yetişkin adları |
| //person[allergy/@ref='Lactose']/@tc | TC_001, TC_002, TC_003 |
Dikkat: son sorgu yalnızca bildirilmiş alerjiyi bulur. "Riskli kişiler" sorusu XPath ile cevaplanamaz — çünkü katkı → alerji zinciri belge dışındadır.
XQuery ile rapor: hangi ürün kimi etkiler?
for $p in doc("persons.xml")//person
let $ean := $p/choice/@ean
let $prod := doc("products.xml")
//product[@ean = $ean]
for $a in $prod/additive/@ref
let $trg := doc("additives.xml")
//additive[@id = $a]/triggers/@allergy
where $trg = $p/allergy/@ref
return <risk tc="{$p/@tc}" ean="{$ean}"
additive="{$a}"/>
<risk tc="TC_001" ean="EAN_00004"
additive="Nisin"/>
<risk tc="TC_002" ean="EAN_00003"
additive="Casein"/>
<risk tc="TC_003" ean="EAN_00003"
additive="Casein"/>
<risk tc="TC_003" ean="EAN_00003"
additive="Sodium_Ascorbite"/>
Aynı sonucu SWRL'de tek satırda yazacağız (S6). Fark: burada zinciri siz kurdunuz; orada kuralı motor uygular ve sonucu ontolojiye kalıcı yazar.
XSLT ile XML'den RDF/XML'e
<xsl:template match="product">
<owl:NamedIndividual
rdf:about="#{@ean}">
<rdf:type rdf:resource="#Product"/>
<hasProductName>
<xsl:value-of select="name"/>
</hasProductName>
<xsl:for-each select="additive">
<Contain rdf:resource="#{@ref}"/>
</xsl:for-each>
</owl:NamedIndividual>
</xsl:template>
<!-- çıktı -->
<owl:NamedIndividual rdf:about="#EAN_00004">
<rdf:type rdf:resource="#Product"/>
<hasProductName>Eti Chocolate
</hasProductName>
<Contain rdf:resource="#Ascorbic_Acid"/>
<Contain rdf:resource="#Nisin"/>
<Contain rdf:resource="#Soy_Lecitin"/>
</owl:NamedIndividual>
Etiket verisini elle ontolojiye girmek yerine bu dönüşümü kullanmak, projeyi gerçek veriyle beslemenin en pratik yoludur.
04
XML Yeter mi?
Ağaç ile graf arasındaki fark ve RDF'e geçiş nedeni.
Ağaç modeli ile graf modeli
XML: ağaç
person
└── allergy @ref="Lactose"
(bağ sadece bir isim)
Referans metindir; anlamı uygulama kodu bilir.
RDF: graf
TC_001 hasAllergy Lactose .
Nisin Triggers Lactose .
EAN_00004 Contain Nisin .
Düğümler paylaşılır; zincir üzerinde çıkarım yapılır.
XML tek başına neden yetmez?
| Eksik | Sonucu | Çözüm katmanı |
| Sıralama anlam taşır | Aynı bilgi, farklı ağaç | RDF (sırasız üçlüler) |
| Bağlar adsız | Anlamı kod bilir | RDF yüklemleri |
| Sınıf/alt sınıf yok | Hiyerarşi kodda | RDFS |
| Kısıt/mantık yok | Çelişki bulunamaz | OWL |
| Çıkarım yok | Yalnızca yazılan bilinir | Reasoner + SWRL |
| Global kimlik yok | Veri birleştirme elle | IRI |
XML yine de vazgeçilmezdir: RDF/XML ve OWL dosyalarımız XML'dir — taşıma katmanı olarak kalır.
Aynı ürün, iki gösterim
products.xml
<product ean="EAN_00003">
<name>Dardanel Ton</name>
<additive ref="Casein"/>
<additive ref="Sodium_Ascorbite"/>
</product>
ALLERGY_FIXED.owl
<owl:NamedIndividual rdf:about="#EAN_00003">
<rdf:type rdf:resource="#Product"/>
<Contain rdf:resource="#Casein"/>
<Contain rdf:resource="#Sodium_Ascorbite"/>
<hasProductName rdf:datatype="&xsd;string">
Dardanel Ton</hasProductName>
</owl:NamedIndividual>
Sözdizimi neredeyse aynı; fark rdf:resource ile kurulan global kimlikli bağdır. Hafta 03'ün konusu tam olarak bu farktır.
Katalog verisi için kontrol listesi
- Her belge bir namespace bildirir; öneki tutarlı kullanın.
- Kimlikler ASCII ve desenle kısıtlı (EAN_[0-9]{5}).
- Ölçü birimini attribute olarak taşıyın (unit="kg").
- Hesaplanan değeri (BMI) kaynak veride tutmayın.
- Katkı → alerji eşlemesini tek bir yerde tutun.
- Her yükleme öncesi XSD ile doğrulayın; hatayı loglayın.
- UTF-8, BOM'suz kaydedin.
- Dönüşümü (XSLT) sürüm kontrolünde tutun; elle düzeltme yapmayın.
Bu liste, Hafta 08'de ontolojiyi gerçek katalog verisiyle beslerken doğrudan uygulanacaktır.
05
Ödev ve Proje Adımı
Kendi ürün kataloğunuzu XML + XSD ile kurun.
Ödev 2 — Katalog XML'i ve şeması
- Kendi seçtiğiniz beş paketli ürün için products.xml yazın.
- Katkı → alerji eşlemesini additives.xml içinde tanımlayın.
- Barkod deseni, yaş aralığı ve alerji enumeration'ı içeren allergy.xsd yazın.
- keyref ile referans bütünlüğünü zorunlu kılın.
- İki hatalı belge üretip doğrulama mesajlarını raporlayın.
Teslim
Dört dosya + 2 sayfalık rapor: tasarım kararları (element/attribute), facet gerekçeleri, hata mesajlarının yorumu.
Çözümü Hafta 03'ün başında ele alacağız.
Değerlendirme ölçütleri
| Ölçüt | Ağırlık | Beklenen |
| Well-formed + valid belgeler | 25% | Doğrulama hatasız geçiyor |
| Şema ifade gücü | 30% | Facet, pattern, enumeration, cardinality kullanılmış |
| Referans bütünlüğü | 20% | key/keyref çalışıyor |
| Tasarım gerekçeleri | 15% | Element/attribute kararları savunulmuş |
| Hata analizi | 10% | cvc kodları doğru yorumlanmış |
Kaynaklar
- W3C — Extensible Markup Language (XML) 1.0, 5th Edition.
- W3C — XML Schema Part 0: Primer; Part 1: Structures; Part 2: Datatypes.
- W3C — Namespaces in XML 1.0; XML Path Language (XPath) 3.1.
- Harold, E. R., Means, W. S. — XML in a Nutshell, O'Reilly.
- Allemang & Hendler — Semantic Web for the Working Ontologist, Bölüm 3 (RDF'e geçiş).
Özet • 1 / 2
XML ve doğrulama
- XML yapıyı taşır, anlamı taşımaz; anlam şemada ve uygulamada kalır.
- Well-formed asgari koşul, valid ise şemaya uygunluktur.
- XSD veri tipi, facet, cardinality ve anahtar kısıtları verir; DTD bunları vermez.
- Kimlik ve meta bilgi attribute, çoklu alan verisi element olur.
- Doğrulama, ontolojiye kirli veri girmesini önleyen ilk savunma hattıdır.
Özet • 2 / 2
Projeye katkısı ve sonraki adım
- Alerji verisi üç belgeye ayrıldı: ürün, katkı, kişi.
- Barkod ve kimlik biçimleri pattern ile güvenceye alındı.
- XSLT ile XML → RDF/XML dönüşümünün iskeleti kuruldu.
- XPath, bildirilmiş veriyi sorgular; risk zincirini sorgulayamaz.
Hafta 03'te
RDF & RDFS: üçlü modeli, graf düşünme, Turtle sözdizimi ve alerji sözlüğünün kurulması.
Ayrıca: Ödev 2'nin ayrıntılı çözümü.
Tekrar Soruları
Kendinizi sınayın
- Bir belge well-formed olup valid olmayabilir mi? Örnek verin.
- Alerji listesini neden attribute değil element yaptık?
- minOccurs="0" ile OWL'daki ≥1 kısıtı arasındaki davranış farkı nedir?
- keyref hangi hatayı yakalar, hangisini yakalamaz?
- XPath ile "riskli kişiler" sorgusu neden yazılamaz?
- Namespace öneki ile IRI arasındaki ilişkiyi açıklayın.
- XSD enumeration ile OWL oneOf arasındaki dünya varsayımı farkı nedir?
- XSLT dönüşümünde rdf:resource neden metin değeri yerine kullanıldı?
Alıştırma • Sınıf içi
Şemayı hatalı belgeye karşı sınayın
Aşağıdaki belgede üç doğrulama hatası vardır. Bulun, cvc mesajını tahmin edin ve düzeltin.
<products count="two">
<product ean="EAN_105">
<additive ref="Nisin"/>
<name>Test Bar</name>
</product>
</products>
İpucu
Sırayla düşünün: attribute tipi, pattern uyumu, xs:sequence içindeki element sırası.
Çözüm Hafta 03'ün ödev çözümü bölümünde.